﻿using System.Linq;
using Missbot.Common;
using Missbot.Core.Base;
using Missbot.Core.Cache;
using Dolany.UtilityTool;
using JetBrains.Annotations;
using Missbot.AIModule.Base;
using Missbot.AIModule.OnlineStore;
using Missbot.AIModule.Pet;
using Missbot.Model.MsgInfos;

namespace Missbot.AIModule.Gaming.SegmentAttach
{
    [UsedImplicitly]
    public class SegmentAttachMod : IAIModule
    {
        public override string Name => "宝藏碎片";

        #region Svcs

        public SegmentSvc SegmentSvc { get; set; }
        public HonorSvc HonorSvc { get; set; }
        public WaiterSvc WaiterSvc { get; set; }

        #endregion

        [ModuleEnter(Command = "领取宝藏碎片", Description = "领取一张宝藏碎片（和另一块碎片拼接后，将获得宝藏！）", DailyLimit = 1)]
        public bool TakeSegment(InboxSession session)
        {
            var segment = SegmentSvc.RandSegment();
            var record = SegmentRecordDA.Get(session.User.ID);
            record.Segment = segment.Name;
            record.IsRare = Rander.RandInt(100) > 90;
            record.Update();

            var buffer = new OutputBuffer(session);
            buffer.Add("你领取到了新的宝藏碎片！");
            buffer.Add(segment.ToString());
            buffer.AddFile(segment.FileID);

            var treasure = SegmentSvc.FindTreasureBySegment(record.Segment);
            buffer.Add($"可开启宝藏：【{treasure.Name}】");
            if (record.IsRare)
            {
                buffer.Add("🎁恭喜你领取到了稀有碎片，拼接后将得到双倍奖励！");
            }

            buffer.Send();
            return true;
        }

        [ModuleEnter(Command = "查看宝藏碎片", Description = "查看指定的宝藏碎片的信息", SyntaxHint = "[宝藏碎片名]")]
        public bool ViewSegment(InboxSession session, string name)
        {
            var segment = SegmentSvc.FindSegmentByName(name);
            if (segment == null)
            {
                session.SendBack("未找到指定的宝藏碎片");
                return false;
            }

            var treasure = SegmentSvc.FindTreasureBySegment(name);
            var msg = $"{segment}\n可开启宝藏：{treasure.Name}";

            session.SendBack(msg, segment.FileID);
            return true;
        }

        [ModuleEnter(Command = "我的宝藏碎片", Description = "查看自己持有的宝藏碎片的信息")]
        public bool MySegment(InboxSession session)
        {
            var record = SegmentRecordDA.Get(session.User.ID);
            if (string.IsNullOrEmpty(record.Segment))
            {
                session.SendBack("你尚未持有任何宝藏碎片！");
                return false;
            }

            var segment = SegmentSvc.FindSegmentByName(record.Segment);
            if (segment == null)
            {
                session.SendBack("未找到指定的宝藏碎片");
                return false;
            }

            var treasure = SegmentSvc.FindTreasureBySegment(record.Segment);
            var buffer = new OutputBuffer(session);
            buffer.Add(segment.ToString());
            buffer.Add($"可开启宝藏：{treasure.Name}");
            buffer.AddFile(segment.FileID);

            if (record.IsRare)
            {
                buffer.Add("【稀有】：拼接后将得到双倍奖励！");
            }

            buffer.Send();
            return true;
        }

        [ModuleEnter(Command = "查看宝藏", Description = "查看指定的宝藏的信息", SyntaxHint = "[宝藏名]")]
        public bool ViewTreasure(InboxSession session, string name)
        {
            var treasure = SegmentSvc.FindTreasureByName(name);
            if (treasure == null)
            {
                session.SendBack("未找到指定的宝藏");
                return false;
            }

            session.SendBack(treasure.Format(), treasure.FileID);
            return true;
        }

        [ModuleEnter(Command = "我的宝藏记录", Description = "查看自己开启过的宝藏记录")]
        public bool MyTreasureRecord(InboxSession session)
        {
            var record = SegmentRecordDA.Get(session.User.ID);
            if (record.TreasureRecord.IsNullOrEmpty())
            {
                session.SendBack("你还没有开启过任何宝藏！");
                return false;
            }

            var buffer = new OutputBuffer(session);
            buffer.Add(record.TreasureRecord.Select(p => $"{p.Key}：{p.Value}次").ToList());
            buffer.Add($"总计：{record.TreasureRecord.Sum(p => p.Value)}次");

            var finalMsg = $"终极宝藏：{record.FinalTreasureCount}次";
            if (record.CanOpenFinalTreasure())
            {
                finalMsg += $"(还可开启{record.TreasureRecord.Values.Min() - record.FinalTreasureCount}次)";
            }

            buffer.Add(finalMsg);

            buffer.Send();
            return true;
        }

        [ModuleEnter(Command = "开启终极宝藏", Description = "开启过所有宝藏之后，可以开启传说中的终极宝藏！")]
        public bool OpenFinalTreasure(InboxSession session)
        {
            var record = SegmentRecordDA.Get(session.User.ID);
            if (!record.CanOpenFinalTreasure())
            {
                session.SendBack("很遗憾，你还不能开启终极宝藏，继续努力吧！（开启过所有其他宝藏才能开启终极宝藏！）");
                return false;
            }

            var options = new[] { "获取500金币", "随机获取商店售卖的一件商品*5", "宠物获取50点经验值", "捞瓶子机会*5(仅当日有效)" };
            var selectedIdx = WaiterSvc.WaitForOptions(session, "请选择你要开启的宝藏：", options);
            if (selectedIdx < 0)
            {
                session.SendBack("你已经放弃了思考！");
                return false;
            }

            switch (selectedIdx)
            {
                case 0:
                {
                    var osPerson = OSPersonDA.GetPerson(session.User.ID);
                    osPerson.Golds += 500;
                    osPerson.Update();

                    session.SendBack($"恭喜你获得了 {500.CurencyFormat()}！");
                    break;
                }
                case 1:
                {
                    var items = TransHelper.GetDailySellItems();
                    var randItem = items.RandElement();

                    session.SendBack($"恭喜你获得了 {randItem.Name}*5！");

                    var collo = ItemCollectionDA.Get(session.User.ID);
                    var msg = collo.ItemIncome(randItem.Name, 5);
                    if (!string.IsNullOrEmpty(msg))
                    {
                        session.SendBack(msg);
                    }

                    break;
                }
                case 2:
                {
                    var pet = PetRecordDA.Get(session.User.ID);
                    var msg = pet.ExtGain(50);
                    session.SendBack(msg);
                    break;
                }
                case 3:
                {
                    var dailyLimit = DailyLimitDA.Get(session.User.ID, "DriftBottleAI_FishingBottle");
                    dailyLimit.Decache(5);
                    dailyLimit.Update();

                    session.SendBack("恭喜你获取 捞瓶子机会*5(仅当日有效) ！");
                    break;
                }
            }

            record.FinalTreasureCount++;
            record.Update();

            return true;
        }

        [ModuleEnter(Command = "拼接宝藏碎片", Description = "和其他成员一起拼接宝藏碎片", SyntaxHint = "[@用户名]")]
        public bool AttachSegment(InboxSession session, InstanceUser aimUser)
        {
            if (aimUser.ID == session.User.ID)
            {
                session.SendBack("你无法和自己进行拼接！");
                return false;
            }

            if (aimUser.IsBot)
            {
                session.SendBack("Stupid Human!");
                return false;
            }

            var selfRecord = SegmentRecordDA.Get(session.User.ID);
            if (string.IsNullOrEmpty(selfRecord.Segment))
            {
                session.SendBack("你当前没有任何碎片！");
                return false;
            }

            var aimRecord = SegmentRecordDA.Get(aimUser.ID);
            if (string.IsNullOrEmpty(aimRecord.Segment))
            {
                session.SendBack("对方当前没有任何碎片！");
                return false;
            }

            var treasure = SegmentSvc.FindTreasureBySegment(selfRecord.Segment);
            if (!treasure.IsMatch(selfRecord.Segment, aimRecord.Segment))
            {
                session.SendBack($"拼接失败，碎片不匹配！({selfRecord.Segment}×{aimRecord.Segment})");
                return false;
            }

            selfRecord.AddTreasureRecord(treasure.Name);
            aimRecord.AddTreasureRecord(treasure.Name);

            var selfBonusItems = HonorSvc.RandItems(3);
            var aimBonusItems = HonorSvc.RandItems(3);

            var selfIcRecord = ItemCollectionDA.Get(session.User.ID);
            var aimIcRecord = ItemCollectionDA.Get(aimUser.ID);

            var selfRate = selfRecord.IsRare ? 2 : 1;
            foreach (var item in selfBonusItems)
            {
                selfIcRecord.ItemIncome(item.Name, selfRate);
            }

            var aimRate = aimRecord.IsRare ? 2 : 1;
            foreach (var item in aimBonusItems)
            {
                aimIcRecord.ItemIncome(item.Name, aimRate);
            }

            session.SendGroup(aimUser, treasure.ToString(), treasure.FileID);

            var msg = "拼接成功！\n" +
                      $"@{session.User.FullUserName} 获得了{selfBonusItems.Select(p => $"{p.Name}*{selfRate}").JoinToString(",")} ！\n" +
                      $"@{aimUser.FullUserName} 获得了{aimBonusItems.Select(p => $"{p.Name}*{aimRate}").JoinToString(",")} ！";
            session.SendGroup(aimUser, msg);

            selfRecord.ClearSegment();
            aimRecord.ClearSegment();
            selfRecord.Update();
            aimRecord.Update();

            return true;
        }
    }
}